<template>
  <el-table
    :data="tableData"
    stripe
    :header-cell-style="{ color: '#fff', backgroundColor: '#4977af'}"
    :row-style="{ height: '80px' }"
    @select="handleSelectChange"
    @select-all="handleSelectChange"
    ref="mytableRef"
    class="mytable"
  >
    <el-table-column type="selection" width="55" align="center" v-if="!isExportTable" />

    <el-table-column
      type="index"
      :index="indexMethod"
      label="序号"
      align="center"
      width="60"
    />

    <el-table-column
      v-for="head in heads"
      :key="head.value"
      :label="head.value"
      :width="head.width"
      align="center"
    >
      <template #default="scope">
        <el-input
          v-if="isEditing[scope.$index][head.attribute] && (head.value !== '社团简介' && head.value !== '活动简介')"
          v-model="scope.row[head.attribute]"
          @blur="changeStatus(scope.$index, head.attribute)"
          v-focus
        />

        <el-input
          v-if="isEditing[scope.$index][head.attribute] && (head.value === '社团简介' || head.value === '活动简介')"
          type="textarea"
          :rows="3"
          v-model="scope.row[head.attribute]"
          @blur="changeStatus(scope.$index, head.attribute)"
          v-focus
        />

        <el-select
          v-if="isSelecting[scope.$index][head.attribute]"
          v-model="scope.row[head.attribute]"
          @visible-change="handleVisibleChange($event, scope.$index, head.attribute)"
          v-selectClick
        >
          <div v-if="head.attribute === 'organization'">
            <OrganizationOption></OrganizationOption>
          </div>
          <div v-if="head.attribute === 'role'">
            <el-option
              v-for="item in options['角色']"
              :key="item.value"
              :label="item.label"
              :value="item.value"
            />
          </div>
          <div v-else>
            <el-option
              v-for="item in head.options"
              :key="item.value"
              :label="item.label"
              :value="item.value"
            />
          </div>
        </el-select>

        <p
          :title="scope.row[head.attribute]"
          v-if="
            !isEditing[scope.$index][head.attribute] &&
            !isSelecting[scope.$index][head.attribute] &&
            head.value !== '社团人数'
          "
          @dblclick="changeStatus(scope.$index, head.attribute)"
        >
          <span v-if="store.getters.organizationMap && head.attribute === 'organization'">{{
            store.getters.organizationMap[scope.row[head.attribute]]
          }}</span>
          <span v-else>{{ scope.row[head.attribute] }}</span>
        </p>

        <p
          :title="scope.row[head.attribute]"
          v-if="
            head.value === '社团人数'
          "
        >
          <span>{{ scope.row[head.attribute] }}</span>
        </p>
      </template>
    </el-table-column>
    <slot></slot>
  </el-table>

  <Pagination
    v-if="!isExportTable"
    :pagination="pagination"
    @currentChange="handleCurrentChange"
  />
</template>

<script lang="ts">
export default {
  directives: {
    selectClick: {
      mounted: (el) => {
        el.querySelector("input").click();
      },
    },
  },
};
</script>

<script lang="ts" setup>
import { reactive, ref, toRefs, watch, watchEffect } from "vue";
import lodash from "lodash";
import { ElMessage, ElTable } from "element-plus";
import { useStore } from "vuex";

import type { TableColumnCtx } from "element-plus/es/components/table/src/table-column/defaults";

import { selects } from "@/data/select.ts";
import OrganizationOption from "./OrganizationOption.vue";
import Pagination from "../Pagination.vue";

import { options } from '@/data/select.ts';

import isDateValid from "@/utils/isDateValid.ts";

const store = useStore();

const props = defineProps([
  "tableData",
  "selectedTable",
  "heads",
  "headMap",
  "isExportTable",
  "pagination",
]);
const emits = defineEmits(["selectionChange", "currentChange", "updateCell"]);

const handleCurrentChange = (page: number) => {
  emits("currentChange", page);
};

// 双击编辑状态功能
const isEditing: IObj[] = reactive([]);
const isSelecting: IObj[] = reactive([]);

function initStatus() {
  const obj: IObj = {};
  const selectObj: IObj = {};

  for (const item in props.headMap) {
    const val = props.headMap[item];

    if (selects.includes(item)) {
      selectObj[val] = false;
    } else {
      obj[val] = false;
    }
  }

  for (const item of props.tableData) {
    const deepObj = lodash.cloneDeep(obj);
    isEditing.push(deepObj);

    const deepSelectObj = lodash.cloneDeep(selectObj);
    isSelecting.push(deepSelectObj);
  }
}

watchEffect(() => {
  const tableData = props.tableData;
  initStatus();
});

let beforeValue = "";
const changeStatus = (index: number, attribute: any) => {

  if (
    attribute === "organization" ||
    attribute === 'role'
  ) {
    isSelecting[index][attribute] = !isSelecting[index][attribute];
  } else {
    isEditing[index][attribute] = !isEditing[index][attribute];
  }

  if (isEditing[index][attribute] || isSelecting[index][attribute]) {
    beforeValue = props.tableData[index][attribute];
  } else {
    if (attribute.includes("Time")) {
      // const reg = /^\d{4}-\d{2}-\d{2}$/;
      // const value = props.tableData[index][attribute];

      // const month = +value.substring(5, 7);
      // const date = +value.substring(8, 10);

      if (!isDateValid(props.tableData[index][attribute])) {
        props.tableData[index][attribute] = beforeValue;
        ElMessage({
          message: "格式错误，修改失败",
          type: "info",
        });
      }
    }
  }

  if (
    !isSelecting[index][attribute] &&
    !isEditing[index][attribute] &&
    props.tableData[index][attribute] !== beforeValue
  ) {
    emits("updateCell", index, attribute);
  }
};

const handleVisibleChange = (show: boolean, index: number, attribute: any) => {
  if (!show) {
    changeStatus(index, attribute);
  } 
}

const handleSelectChange = (selection: IObj[]) => {
  // console.log(selection);
  // console.warn(mytableRef.value!.toggleRowSelection);
  emits("selectionChange", selection);
};

const mytableRef = ref<InstanceType<typeof ElTable>>();
watch(
  () => props.tableData,
  () => {
    const selectedTable = [];
    for (const item in props.selectedTable) {
      if (props.selectedTable[item].length != 0) {
        selectedTable.push(...props.selectedTable[item]);
      }
    }

    for (const item of props.tableData) {
      for (const selectItem of selectedTable) {
        if (selectItem.rowId === item.rowId) {
          mytableRef.value?.toggleRowSelection(item, true);
        }
      }
    }
  },
  {
    deep: true,
  }
);

const indexMethod = (index: number) => {
  if (!props.isExportTable) {
    return (
      index + 1 + props.pagination.pageSize * (props.pagination.currentPage - 1)
    );
  } else {
    return index + 1;
  }
};
</script>

<style lang="less" scoped>
.mytable {
  width: 100%;
  height: 59vh;
  p {
    overflow: hidden;
    text-overflow: ellipsis;
    display: -webkit-box;
    -webkit-line-clamp: 2;
    -webkit-box-orient: vertical;
  }

  .operation {
    display: flex;
    align-items: center;
    justify-content: center;

    span {
      color: #3f85ed;
      cursor: pointer;
    }

    .moveup-text,
    .movedown-text {
      color: #666;
    }

    .delete-text {
      margin-left: 20px;
    }

    .move {
      display: inline-flex;
      flex-direction: column;
      font-size: 16px;
      margin-left: 8px;
    }
  }
}
</style>
